import irrlicht;
import std.stdio;

void main()
{
    writeln("Press 'y' if you want to use realtime shadows.\n");
    char i = readln()[0];
    
    immutable bool shadows = (i == 'y');
    
    E_DRIVER_TYPE driverType = driverChoiceConsole();
    
    assert(driverType != E_DRIVER_TYPE.EDT_COUNT);
    
    IrrlichtDevice device = createDevice(driverType, new UintDimension2D(640,480),
                                         16,false,false,false,null);
    
    IVideoDriver driver = device.getVideoDriver();
    ISceneManager smgr = device.getSceneManager();
    
    IAnimatedMesh mesh = smgr.getMesh("media/room.3ds");
    
    smgr.getMeshManipulator().makePlanarTextureMapping(mesh.getMesh(0), 0.004);
    
    ISceneNode node;
    node = smgr.addAnimatedMeshSceneNode(mesh);
    node.setMaterialTexture(0, driver.getTexture("media/wall.jpg"));
    node.getMaterial(0).SpecularColor.set(0,0,0,0);
    
    mesh = smgr.addHillPlaneMesh("myHill", new FloatDimension2D(20,20),
                                           new UintDimension2D(40,40),
                                           null,
                                           0,
                                           new FloatDimension2D(0,0),
                                           new FloatDimension2D(10,10));
    
    node = smgr.addWaterSurfaceSceneNode(mesh.getMesh(0), 3.0, 300.0, 30.0);
    node.setPosition(new FloatVector3D(0,7,0));
    
    node.setMaterialTexture(0, driver.getTexture("media/stones.jpg"));
    node.setMaterialTexture(1, driver.getTexture("media/water.jpg"));
    
    node.setMaterialType(E_MATERIAL_TYPE.EMT_REFLECTION_2_LAYER);
    
    node = smgr.addLightSceneNode(null, new FloatVector3D(0,0,0),
                                  new SColorf(1,.6,.7,1.0),800.0);
    ISceneNodeAnimator anim;
    anim = smgr.createFlyCircleAnimator(new FloatVector3D(0,150,0), 250);
    node.addAnimator(anim);
    
    node = smgr.addBillboardSceneNode(node, new FloatDimension2D(50,50));
    node.setMaterialFlag(E_MATERIAL_FLAG.EMF_LIGHTING, false);
    node.setMaterialType(E_MATERIAL_TYPE.EMT_TRANSPARENT_ADD_COLOR);
    node.setMaterialTexture(0, driver.getTexture("media/particlewhite.bmp"));
    
    IParticleSystemSceneNode ps = smgr.addParticleSystemSceneNode(false);
    IParticleEmitter em = ps.createBoxEmitter(
        new FloatAABBox3D(-7,0,-7,7,1,7),
        new FloatVector3D(0,0.06,0),
        80, 100,
        new SColor(0,255,255,255),
        new SColor(0,255,255,255),
        800,2000,0,
        new FloatDimension2D(10,10),
        new FloatDimension2D(20,20));
        
    ps.setEmitter(em);
    
    IParticleAffector paf = ps.createFadeOutParticleAffector();
    
    ps.addAffector(paf);
    
    ps.setPosition(new FloatVector3D(-70,60,40));
    ps.setScale(new FloatVector3D(2,2,2));
    ps.setMaterialFlag(E_MATERIAL_FLAG.EMF_LIGHTING, false);
    ps.setMaterialFlag(E_MATERIAL_FLAG.EMF_ZWRITE_ENABLE, false);
    ps.setMaterialTexture(0, driver.getTexture("media/fire.bmp"));
    ps.setMaterialType(E_MATERIAL_TYPE.EMT_TRANSPARENT_VERTEX_ALPHA);
    
    IVolumeLightSceneNode n = smgr.addVolumeLightSceneNode(null, -1,
                                                           32, 32,
                                                           new SColor(0,255,255,255),
                                                           new SColor(0,0,0,0));
                                                           
    if(n)
    {
        n.setScale(new FloatVector3D(56,56,56));
        n.setPosition(new FloatVector3D(-120,50,40));
        
        ITexture[] textures;
        for(int g=7; g>0; --g)
        {
            string tmp = "media/portal";
            tmp ~= std.conv.to!string(g);
            tmp ~= ".bmp";
            ITexture t = driver.getTexture(tmp);
            textures ~= t;
        }
        
        ISceneNodeAnimator glow = smgr.createTextureAnimator(textures, 150);
        n.addAnimator(glow);
    }
    
    mesh = smgr.getMesh("media/dwarf.x");
    IAnimatedMeshSceneNode anode;
    
    anode = smgr.addAnimatedMeshSceneNode(mesh);
    anode.setPosition(new FloatVector3D(-50,20,-60));
    
    anode.setPosition(new FloatVector3D(-50,20,-60));
    anode.setAnimationSpeed(15);
    
    anode.addShadowVolumeSceneNode();
    smgr.setShadowColor(new SColor(150,0,0,0));
    
    anode.setScale(new FloatVector3D(2,2,2));
    anode.setMaterialFlag(E_MATERIAL_FLAG.EMF_NORMALIZE_NORMALS, true);
    
    ICameraSceneNode camera = smgr.addCameraSceneNodeFPS();
    camera.setPosition(new FloatVector3D(-50,50,150));
    
    device.getCursorControl().setVisible(false);
    
    int lastFPS = -1;
    while(device.run())
    if(device.isWindowActive())
    {
        driver.beginScene(true,true);
        
        smgr.drawAll();
        
        driver.endScene();
        
        immutable fps = driver.getFPS();
        
        if(lastFPS != fps)
        {
            wstring str = "Irrlicht Engine - SpecialFX example with D [";
            str ~= driver.getName();
            str ~= "] FPS:";
            str ~= std.conv.to!wstring(fps);
            
            device.setWindowCaption(str);
            lastFPS = fps;
        }
    }
    device.drop();
}